/*********************************************************************************
 *      Copyright:  (C) 2022 Zhukaifa（928085237@qq.com）
 *                  All rights reserved.
 *
 *       Filename:  parse_data.c
 *    Description:  This file is used to parse out APN MCC MNC 

 *                 
 *        Version:  1.0.0(28/07/22)
 *         Author:  Zhukaifa（928085237@qq.com）
 *      ChangeLog:  1, Release initial version on "28/07/22 21:52:04"
 *                 
 ********************************************************************************/

#include <stdio.h>
#include <string.h>
#include <libxml2/libxml/xmlmemory.h>
#include <libxml2/libxml/parser.h>
#include <libxml/xmlversion.h>
#include <libxml/xmlstring.h>


#include "parse_data.h"
 
 
/*********************************************************************************
 *
 *           Name:  analy_apn.c
 *    Description:  Parse apn from xml file  
 *                 
 *        Input args:     
 *                    file_name: .XML File path 
 *
 *       Output args: 
 *                    cna:   Structure for storing apn
 *
 *      return value:
 *                    void
 *
 *                 
 ********************************************************************************/


 
 
 
void parse_apn(char *file_name, cna_t *cna)
{
        xmlDocPtr       doc;        //文档指针
        xmlNodePtr      cur;        //根节点
        xmlChar         *mcc;       //移动国家代码
        xmlChar         *mnc;       //移动网络代码
        xmlChar         *apn;       //PPP拨号APN
 
        /*      目标mcc与mnc      */
 
        if( !file_name )
        {
                printf("Invalid input arguments\n");
        }
 
        doc = xmlReadFile(file_name, "UTF-8", XML_PARSE_RECOVER);  //读入需要解析的xml文件
        if (doc == NULL)
        {
                printf("Failed to read xml file:%s\n", file_name);
                goto cleanup;
        }
 
        cur = xmlDocGetRootElement(doc);  //获取根节点
        if (cur == NULL)
        {
                printf("Root is empty.\n");
                goto cleanup;
        }
 
        if ( xmlStrcmp(cur->name, (const xmlChar *)"apns") )    //判断根节点是否正确，注意强制类型转换
        {
                printf("The root is not apns.\n");
                goto cleanup;
        }
 
        cur = cur->xmlChildrenNode;     //由根节点指向子节点
 
        while (cur != NULL)
        {
                if ( xmlStrcmp(cur->name, (const xmlChar *)"apn")==0 )  //现在的cur->name子节点的name，判断name里有没有apn，若有，往下走
                {
                        /*      xmlGetProp取出其属性值      */
                        mcc = xmlGetProp(cur, "mcc");
                        mnc = xmlGetProp(cur, "mnc");
 
                        if( xmlStrcmp(mcc, (const xmlChar *)cna->mcc)==0 && xmlStrcmp(mnc, (const xmlChar *)cna->mnc)==0 )  //若mcc和mnc是460 03同时成立，则获取该子节点APN
                        {
                                apn = xmlGetProp(cur, "apn");
                                strncpy(cna->apn ,BAD_CAST(apn), sizeof(cna->apn));
                                printf("mcc:%s mnc:%s apn:%s \n",cna->mcc, cna->mnc, cna->apn);
 
                                break;
                        }
                }
                cur = cur->next;//若不满足条件则指向下一个子节点
        }
cleanup:
        if (doc)
        {
                xmlFreeDoc(doc);
        }
 
}
 
 
/*********************************************************************************
 *
 *           Name:  parse_mccmnc 
 *
 *    Description:  Parse mcc mnc from AT instruction

 *                 
 *        Input args:     
 *                      com:  Structure for storing com port attributes
 *
 *       Output args:  
 *                      Structure for storing apn
 *
 *      return value:
 *                      <0    failure
 *                      =0    success
 *                 
 ********************************************************************************/




int parse_mccmnc(comport_t *com, cna_t *cna)//检测sim卡是否存在
{

	int     rv;
	int     i;
	char    buf[128];
	char   *ptr;
	char    str[16]; 
	
	char   *p1;
	char   *p2;
	char    p2_buf[8];

	char    mc_buf[3];
	char    mn_buf[3];

	memset(buf, 0, sizeof(buf));
	memset(mc_buf, 0, sizeof(mc_buf));
	memset(mn_buf, 0, sizeof(mn_buf));

	if(!com|| !cna)
	{
		log_error("%s The argument invalid!\n", __func__);
		return -1;
	}
	rv= at_cmd_send(com, "AT+QNWINFO\r", "+QNWINFO", buf, sizeof(buf), 3000);
	if(rv<0)
	{

		log_error("%s function failure", __func__);
		return -1;
	}

	log_info("%s, successfully!\n", __func__);

/*+QNWINFO: "CDMA1X","46003","CDMA BC0",283*/
	ptr=strstr(buf,"CDMA1X");
/*str:CDMA1X","46003",*/	
	strncpy(str, ptr, sizeof(str));


	p1=strtok(str,"\",\"");//CDMA1X
	p2=strtok(NULL,"\",\"");//46003


	memset(p2_buf, 0, sizeof(p2_buf));
	strncpy(p2_buf, p2, sizeof(p2_buf));
	for(i=0; i<3; i++)
	{
		strncat(cna->mcc, &p2_buf[i],1);
	}
	strncat(cna->mnc, &p2_buf[3],2);

	return 0;

}
 
 
/*********************************************************************************
 *
 *           Name: set_apn
 *
 *    Description:   Send AT instruction to set APN
 *                 
 *        Input args:     
 *                      com:  Structure for storing com port attributes
 *       Output args: 
 *
 *      return value:
 *                      <0    failure
 *                      =0    success

 *                 
 ********************************************************************************/



int set_apn(comport_t *com, cna_t *cna)//检测sim卡是否存在
{

	int     rv;
	char    buf[32];
	char    str[64];

	memset(buf, 0, sizeof(buf));
	memset(str, 0, sizeof(str));

	if(!com|| !cna)
	{
		log_error("%s The argument invalid!\n", __func__);
		return -1;
	}

//设置参数分别表示【顺序】、【IP类型】、【APN名】
	snprintf(str, sizeof(str), "AT+CGDCONT=1, \"IP\",\"%s\"\r", cna->apn);
	rv= at_cmd_send(com, str, "OK", buf, sizeof(buf), 3000);
	if(rv<0)
	{

		log_error("%s function failure", __func__);
		return -1;
	}

	log_info("%s, successfully!\n", __func__);

	return 0;

}

